#include "Logger.hpp"

namespace sl
{
	std::string LogType::myTypes[LogType::Type::Count] = { "", "Info", "Warning", "Error" };

	std::string LogType::ToString(LogType::Type type)
	{
		return myTypes[type];
	}

	//###########################################################################################

	Log::Log() : myLogType(LogType::None)
	{}

	Log::Log(LogType::Type type) : myLogType(type)
	{}

	Log::~Log()
	{}

	Log* Log::SetLogType(LogType::Type type)
	{
		myLogType = type;
		return this;
	}

	Log* Log::Open(const std::string& filename)
	{
		return this;
	}

	Log* Log::Close()
	{
		return this;
	}

	Log* Log::Write(const std::string& text)
	{
		return Write(LogType::None, text);
	}

	Log* Log::Write(LogType::Type type, const std::string& text)
	{
		return this;
	}

	//###########################################################################################

	Logger::Logger() : Log(LogType::None), myStream(std::cout)
	{
		Open();
	}

	Logger::~Logger()
	{
		Close();
	}

	Logger* Logger::Open(const std::string& filename)
	{
		return this;
	}

	Logger* Logger::Close()
	{
		return this;
	}

	Logger* Logger::Write(const std::string& text)
	{
		return Write(LogType::None, text);
	}

	Logger* Logger::Write(LogType::Type type, const std::string& text)
	{
		myStream << LogType::ToString(type) << ((type != LogType::None) ? ": " : "") << text << "\n";
		return this;
	}

	std::ostream& Logger::operator()()
	{
		return myStream;
	}

	// ###################################################################

	FileLogger::FileLogger(const std::string& filename) : Log(LogType::None), myStream(filename, std::ios_base::out)
	{}

	FileLogger::~FileLogger()
	{
		Close();
	}

	FileLogger* NewFileLogger(const std::string& filename)
	{
		return new FileLogger(filename);
	}

	FileLogger* FileLogger::Open(const std::string& filename)
	{
		if (!myStream.is_open())
			myStream.open(filename, std::ios_base::out);

		if (myStream.is_open())
			return this;

		return NULL;
	}

	FileLogger* FileLogger::Close()
	{
		myStream.close();
		return this;
	}

	FileLogger* FileLogger::Write(const std::string& text)
	{
		return Write(LogType::None, text);
	}

	FileLogger* FileLogger::Write(LogType::Type type, const std::string& text)
	{
		myStream << LogType::ToString(type) << ((type != LogType::None) ? ": " : "") << text << "\n";
		return this;
	}

	std::ofstream& FileLogger::operator()()
	{
		return myStream;
	}
}